package cn.fx.baseweb.test.controller;

import cn.fx.framework.utils.ReturnResult;
import cn.hutool.json.JSONUtil;
import org.apache.hc.client5.http.entity.mime.MultipartEntityBuilder;
import org.apache.hc.client5.http.impl.classic.CloseableHttpResponse;
import org.apache.hc.core5.http.ContentType;
import org.apache.hc.core5.http.HttpEntity;
import org.apache.hc.core5.http.io.entity.EntityUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.util.ClassUtils;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;

import static cn.fx.framework.web.Http5Util.post;

/**
 * 文件上传，示例1
 * 发起文件上传：/test/upload/send_upload_file
 * 执行上传文件保存：/test/upload/save_upload_file
 *
 * @author
 */
@RestController
@RequestMapping("/test/upload/")
public class FileUploadController {
    private final static Logger logger = LoggerFactory.getLogger(FileUploadController.class);

    //获取Class资源目录:classes/的物理目录
    private static final String UPLOADED_FOLDER = ClassUtils.getDefaultClassLoader().getResource(".").getPath();

    @GetMapping("file")
    public String index() {
        return "upload/file";
    }

    /**
     * 发起文件上传
     *
     * @return
     */
    @GetMapping("send_upload_file")
    public ReturnResult testPostFile() {
        ReturnResult returnResult = new ReturnResult();
        String url = "http://localhost:8080/test/upload/save_upload_file";
        try {
            // 1、构建File参数
            File file = new File(UPLOADED_FOLDER + "/static/abc.txt");

            MultipartEntityBuilder builder = MultipartEntityBuilder.create();
            builder.addBinaryBody("file", file, ContentType.MULTIPART_FORM_DATA, file.getName());

            // 2、构建其他参数
            builder.addTextBody("token", "tokkkkkeeeennnn", ContentType.TEXT_PLAIN);
            builder.addTextBody("key", "keeeeeeeeey", ContentType.TEXT_PLAIN);
            HttpEntity multipartEntity = builder.build();

            // 3、需要加 header，在这里加
            Map<String, String> headers = new HashMap<>();

            // 4、发起http请求
            CloseableHttpResponse httpResponse = post(url, "POST", headers, multipartEntity);
            // 5、返回结果，异常处理
            returnResult.setCode(httpResponse.getCode());
            returnResult.setMessage(httpResponse.getReasonPhrase());

            if (httpResponse.getCode() == 200) {
                String resStr = EntityUtils.toString(httpResponse.getEntity());
                ReturnResult result = JSONUtil.toBean(resStr, ReturnResult.class);
                //根据目标服务器保存文件情况设置返回结果
                returnResult = result;
                if(result.getCode() == 200) {
                    logger.info(result.getMessage());
                }else {
                    logger.error(returnResult.getMessage());
                }
            }

        } catch (Exception e) {
            returnResult.setMessage(e.getMessage());
        }
        return returnResult;
    }

    /**
     * 执行文件上传：
     * 接收上传文件，然后保存，返回访问地址
     *
     * @param file
     * @return
     */
    @PostMapping("save_upload_file")
    public ReturnResult singleFileUpload(@RequestParam("file") MultipartFile file, @RequestParam String token, @RequestParam String key) {
        ReturnResult returnResult = new ReturnResult();

        if (file.isEmpty()) {
            returnResult.setMessage("文件为空,请选择你的文件上传");
            returnResult.setCode(4000);
        } else if (file.getSize() > 1024) {  //1024*1024*10
            returnResult.setCode(4001);
            returnResult.setMessage("文件大小不得超过10M。");
        } else {
            try {
                saveFile(file);
                logger.info("上传文件保存成功：" + file.getOriginalFilename());
                System.out.println("token:" + token + "    key:" + key);
            } catch (IOException e) {
                returnResult.setMessage(e.getMessage());
                returnResult.setCode(4002);
            }
            returnResult.setMessage("上传文件" + file.getOriginalFilename() + "成功");
            returnResult.setData("/static/upload_files/" + file.getOriginalFilename());
            returnResult.setCode(200);
        }
        return returnResult;
    }

    private void saveFile(MultipartFile file) throws IOException {
        File path = new File(UPLOADED_FOLDER + "/static/upload_files/" + file.getOriginalFilename());
        file.transferTo(path);
    }

    @GetMapping("uploadStatus")
    public String uploadStatus(@ModelAttribute("msg") String msg, @ModelAttribute("url") String url) {
        return "upload/uploadStatus";
    }
}